(define (make-frame variables values)
  (if (null? variables)
    '()
    (cons
      (cons (car variables) (car values))
      (make-frame (cdr variables) (cdr values)))))

(define (first-binding frame)
  (car frame))
(define (rest-bindings frame)
  (cdr frame))
(define (add-binding-to-frame! var val frame)
  (cons (cons var val) frame))

; extend-environment 不需要修改
(define (extend-environment vars vals base-env)
  (if (= (length vars) (length vals))
    (cons (make-frame vars vals) base-env)
    (if (< (length vars) (length vals))
      (error "Too many arguments supplied" vars vals)
      (error "Too few arguments supplied" vars vals))))

(define (lookup-variable-value var env)
  (define (env-loop env)
    (define (scan frame)
      (cond ((null? frame)
              (env-loop (enclosing-environment env))
            ((eq? var (car (first-binding frame)))
              (cdr (first-binding frame)))
            (else (scan (rest-bindings frame))))))
    (if (eq? env the-empty-environment)
      (error "Unbound variable " var)
      (let ((frame (first-frame env))
        (scan frame)))))
  (env-loop env))
(define (set-variable-value! var val env)
  (define (env-loop env)
    (define (scan frame)
      (cond ((null? frame)
              (env-loop (enclosing-environment env))
            ((eq? var (car (first-binding frame)))
              (set-cdr! (first-binding frame) val))
            (else (scan (rest-bindings frame))))))
    (if (eq? env the-empty-environment)
      (error "Unbound variable " var)
      (let ((frame (first-frame env))
        (scan frame)))))
  (env-loop env))
(define (define-variable! var val env)
  (let ((frame (first-frame env)))
    (define (scan frame)
      (cond ((null? frame)
              (add-binding-to-frame! var val frame))
            ((eq? var (car (first-binding frame)))
              (set-cdr! (first-binding frame) val))
            (else (scan (rest-bindings frame)))))
    (scan (first-frame env))))
